using System;
using System.Collections.Generic;
using System.Text;
using TTDotNet.Util;
using TTDotNet.Engine.Companies;
using TTDotNet.Engine.Files;
using Microsoft.DirectX;
using TTDotNet.Engine.Networks;
using Microsoft.DirectX.Direct3D;

namespace TTDotNet.Engine.Vehicles
{
    public class RoadVehicle : Vehicle
    {
        
        public float xMod;
        public float zMod;

        private float lastYHeight;
        private float yHeight;

        private bool userControlled;

        private int currentStep;
        private RoadPath following;

        private static List<VehicleInfo> info;

        static RoadVehicle()
        {
            RoadVehicleLoader loader = new RoadVehicleLoader();
            info = loader.GetVehicleInfo();
        }

        public static List<VehicleInfo> VehicleInfos
        {
            get { return info; }
        }

        public RoadVehicle(string name, VehicleInfo info, Company company, DateTime date, Vector3 location) : base(name,info, company, date, location)
        {
            xMod = 0;
            zMod = 0;
        }

        public void SetNewRoadPath(RoadPath path)
        {
            following = path;
        }

        public override void DoMove(float fractionElapsed)
        {
            float incX = 0;
            float incY = 0;
            float incZ = 0;
            float xRot = 0;
            float yRot = 0;
            float zRot = 0;

            float incline = Geometry.RadianToDegree((float)Math.Atan(2 / Game.heightScale));

            needNewInterimDestination = false;

            if (following != null)
            {
                if (following.Source.Coordinate.X != following.Destination.Coordinate.X)
                    incX = vehicleInfo.MaxSpeed * fractionElapsed * roadSpeedScale;
                else
                    incZ = vehicleInfo.MaxSpeed * fractionElapsed * roadSpeedScale;

                if (incX != 0 && following.Source.Coordinate.X > following.Destination.Coordinate.X)
                    incX *= -1;

                if (incZ != 0 && following.Source.Coordinate.Z > following.Destination.Coordinate.Z)
                    incZ *= -1;

                float lastY = Location.Y  * Game.heightScale;;

                incY = following.GetPathHeightAt(Location.X, Location.Z);

                if (incX > 0)
                {
                    incX = Location.X + incX;
                    incZ = ObjectCoordinate.Z + 0.25f;
                    yRot = 90;

                    if (incY - lastY > 0) zRot = -incline;
                    else if (incY - lastY < 0 && incY != -1) zRot = incline;
                }
                else if (incX < 0) 
                {
                    incX = Location.X + incX;
                    incZ = ObjectCoordinate.Z - 0.25f;
                    yRot = 270;

                    if (incY - lastY > 0) zRot = incline;
                    else if (incY - lastY < 0 && incY != -1) zRot = -incline;
                }
                else if (incZ > 0)
                {                    
                    incX = ObjectCoordinate.X - 0.25f;
                    incZ = Location.Z + incZ;
                    yRot = 0;

                    if (incY - lastY > 0) xRot = incline;
                    else if (incY - lastY < 0 && incY != -1) xRot = -incline;
                }
                else if (incZ < 0)
                {
                    incX = ObjectCoordinate.X + 0.25f;
                    incZ = Location.Z + incZ;
                    yRot = 180;

                    if (incY - lastY > 0) xRot = incline;
                    else if (incY - lastY < 0 && incY != -1) xRot = -incline;
                }

                //float newX = incX + Location.X;
                //float newZ = incZ + Location.Z;


                Vector3 location = Location;
                location.X = incX;
                if(incY != -1)
                    location.Y = incY / Game.heightScale;
                location.Z = incZ;
                Location = location;

                if (ObjectDDDCoordinate.Equals(following.Destination.Coordinate))
                    needNewInterimDestination = true;

                Vector3 rotation = Rotation;
                rotation.X = xRot;
                rotation.Y = yRot;
                rotation.Z = zRot;
                Rotation = rotation;

                //objectLocation.X += 0.01f;

                //Vector3 meshLocation = objectLocation;

                //objectMesh.Mesh.MoveInstance(meshLoc, objectMesh.GUID);
            }
            else
            {
                needNewInterimDestination = true;
            }

            //if (!(DDDCoordinate.Equals(currentDestinationCoord)) && currentDestinationCoord.X != -1)
            //{
            //    needNewInterimDestination = false;
            //}

            //    if (!needNewInterimDestination && !IsStopped || userControlled)
            //    {
            //        if (!userControlled)
            //        {

            //            if (Coordinate.X == currentDestination.X)
            //            {
            //                objectLocation.X = currentDestination.X;
            //                zSpeed = vehicleInfo.MaxSpeed * fractionElapsed * roadSpeedScale;

            //                zMod = 0;
            //                xMod = -0.25f;

            //                if (currentDestination.Z < Coordinate.Z)
            //                {
            //                    zSpeed *= -1;
            //                    RotateTo(new Vector3(objectRotation.X, 180, objectRotation.Z));
            //                    xMod = 0.25f;
            //                }
            //                else
            //                {
            //                    RotateTo(new Vector3(objectRotation.X, 0, objectRotation.Z));
            //                }

            //                xSpeed = 0;
            //            }
            //            else if (Coordinate.Z == currentDestination.Z)
            //            {
            //                xSpeed = vehicleInfo.MaxSpeed * fractionElapsed * roadSpeedScale;
            //                objectLocation.Z = currentDestination.Z;

            //                xMod = 0;
            //                zMod = 0.25f;

            //                if (currentDestination.X < Coordinate.X)
            //                {
            //                    xSpeed *= -1;
            //                    zMod = -0.25f;
            //                    RotateTo(new Vector3(objectRotation.X, 270, objectRotation.Z));
            //                }
            //                else
            //                {
            //                    RotateTo(new Vector3(objectRotation.X, 90, objectRotation.Z));
            //                }

            //                zSpeed = 0;
            //            }
            //        }

            //        lastYHeight = yHeight;
            //        yHeight = Game.gameWorld.Map.GetTile(Coordinate).GetRoadHeight(new System.Drawing.PointF(objectLocation.X, objectLocation.Z));

            //        objectLocation.X = objectLocation.X + xSpeed;
            //        objectLocation.Y = yHeight;
            //        objectLocation.Z = objectLocation.Z + zSpeed;

            //        if (objectLocation.X > Game.gameWorld.Map.Width - 1) { objectLocation.X = Game.gameWorld.Map.Width - 1; }
            //        if (objectLocation.Z > Game.gameWorld.Map.Length - 1) { objectLocation.Z = Game.gameWorld.Map.Length - 1; }

            //        Vector3 meshLoc = objectLocation;
            //        meshLoc.X += xMod;
            //        meshLoc.Z += zMod;

            //        if (meshLoc.X > Game.gameWorld.Map.Width - 1) { meshLoc.X = Game.gameWorld.Map.Width - 1; }
            //        if (meshLoc.Z > Game.gameWorld.Map.Length - 1) { meshLoc.Z = Game.gameWorld.Map.Length - 1; }

            //        objectMesh.Mesh.MoveInstance(meshLoc, objectMesh.GUID);

            //        lastYHeight = yHeight;
            //        yHeight = Game.gameWorld.Map.GetTile(Coordinate).GetRoadHeight(new System.Drawing.PointF(objectLocation.X, objectLocation.Z));

            //        float incline = Game.gameWorld.Map.GetTile(Coordinate).GetRoadIncline();

            //        if (xSpeed == 0)
            //        {
            //            if (yHeight - lastYHeight < 0)
            //            {
            //                if (zSpeed > 0)
            //                {
            //                    RotateTo(new Vector3(incline, objectRotation.Y, 0));
            //                }
            //                else
            //                {
            //                    RotateTo(new Vector3(incline * -1, objectRotation.Y, 0));
            //                }
            //            }
            //            else
            //            {
            //                if (zSpeed > 0)
            //                {
            //                    RotateTo(new Vector3(incline * -1, objectRotation.Y, 0));
            //                }
            //                else
            //                {
            //                    RotateTo(new Vector3(incline, objectRotation.Y, 0));
            //                }
            //            }
            //        }
            //        else
            //        {
            //            if (yHeight - lastYHeight < 0)
            //            {
            //                if (xSpeed > 0)
            //                {
            //                    RotateTo(new Vector3(0, objectRotation.Y, incline * -1));
            //                }
            //                else
            //                {
            //                    RotateTo(new Vector3(0, objectRotation.Y, incline));
            //                }
            //            }
            //            else
            //            {
            //                if (xSpeed > 0)
            //                {
            //                    RotateTo(new Vector3(0, objectRotation.Y, Game.gameWorld.Map.GetTile(Coordinate).GetRoadIncline()));
            //                }
            //                else
            //                {
            //                    RotateTo(new Vector3(0, objectRotation.Y, Game.gameWorld.Map.GetTile(Coordinate).GetRoadIncline() * -1));
            //                }
            //            }
            //        }

            //}

            //try
            //{

            if (ObjectDDDCoordinate.Equals(GetFinalDestination()))
                ArrivedAtFinalDestination();

            //    if (DDDCoordinate.Equals(GetFinalDestination()))
            //    {
            //        needNewInterimDestination = true;
            //        ArrivedAtFinalDestination();
            //    }
            //    else if (DDDCoordinate.Equals(currentDestinationCoord))
            //    {
            //        needNewInterimDestination = true;
            //    }
            //    else if (currentDestination.X == -1)
            //    {
            //        needNewInterimDestination = true;
            //    }

            //}
            //catch (Exception e)
            //{

            //}
            
        }

        public void TakeControl(bool value)
        {
            userControlled = value;
        }

    }
}
